package cn.lili.controller.payment;

import cn.lili.common.aop.annotation.PreventDuplicateSubmissions;
import cn.lili.common.enums.ResultCode;
import cn.lili.common.exception.ServiceException;
import cn.lili.common.security.AuthUser;
import cn.lili.common.security.context.UserContext;
import cn.lili.common.security.enums.SceneEnums;
import cn.lili.common.utils.ResultUtil;
import cn.lili.common.vo.ResultMessage;
import cn.lili.modules.member.client.UserClient;
import cn.lili.modules.member.entity.dos.User;
import cn.lili.modules.payment.entity.vo.WalletVO;
import cn.lili.modules.verification.client.VerificationServiceClient;
import cn.lili.modules.verification.entity.enums.VerificationEnums;
import cn.lili.modules.wallet.service.WalletService;
import cn.lili.modules.wallet.service.WithdrawApplyService;
import com.pojos.UserRes;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.RequiredArgsConstructor;
import org.springframework.web.bind.annotation.*;

import javax.validation.constraints.Max;
import javax.validation.constraints.Min;
import javax.validation.constraints.Pattern;

/**
 * 买家端,会员余额接口
 *
 * @author pikachu
 * @since 2020/11/16 10:07 下午
 */
@RestController
@Api(tags = "买家端,会员余额接口")
@RequestMapping("/payment/wallet")
@RequiredArgsConstructor
public class WalletController {

    /**
     * 会员
     */

    private final UserClient userClient;
    /**
     * 会员余额
     */
    private final WalletService walletService;
    /**
     * 会员余额
     */
    private final WithdrawApplyService withdrawApplyService;
    /**
     * 验证码
     */
    private final VerificationServiceClient verificationServiceClient;

    @GetMapping
    @ApiOperation(value = "查询用户钱包余额")
    public ResultMessage<WalletVO> get() {
        AuthUser authUser = UserContext.getCurrentUser();
        if (authUser != null) {
            if (SceneEnums.URBAN_SUBSTATION.equals(authUser.getScene())) {
                return ResultUtil.data(walletService.getWalletVO(UserContext.getCurrentUser().getId()));
            }else {
                return ResultUtil.data(walletService.getWalletVO(UserContext.getCurrentId()));
            }
        }
        throw new ServiceException(ResultCode.USER_NOT_LOGIN);
    }

    @GetMapping(value = "/{userId}")
    @ApiOperation(value = "查询用户钱包余额")
    public ResultMessage<WalletVO> get(@PathVariable String userId) {
        AuthUser authUser = UserContext.getCurrentUser();
        if (authUser != null && authUser.getScene().equals(SceneEnums.MANAGER)) {
            return ResultUtil.data(walletService.getWalletVO(userId));
        }
        throw new ServiceException(ResultCode.USER_NOT_LOGIN);
    }

    @PostMapping(value = "/set-password")
    @ApiOperation(value = "设置支付密码")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "password", value = "支付密码", required = true, dataType = "String", paramType = "query")
    })
    public ResultMessage<Object> setPassword(String password, @RequestHeader String uuid) {
        AuthUser authUser = UserContext.getCurrentUser();
        //校验当前用户是否存在
        User member = userClient.getById(authUser.getId());
        if (member == null) {
            throw new ServiceException(ResultCode.USER_NOT_EXIST);
        }
        //校验验证码
        if (verificationServiceClient.check(uuid, SceneEnums.MEMBER, VerificationEnums.WALLET_PASSWORD)) {
            walletService.setUserWalletPassword(password);
            throw new ServiceException(ResultCode.SUCCESS);
        } else {
            throw new ServiceException(ResultCode.VERIFICATION_ERROR);
        }

    }

    @PostMapping(value = "/update-password/ordinary")
    @ApiOperation(value = "普通方式进行支付密码的修改")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "oldPassword", value = "旧支付密码", required = true, dataType = "String", paramType = "query"),
            @ApiImplicitParam(name = "newPassword", value = "新支付密码", required = true, dataType = "String", paramType = "query")
    })
    public ResultMessage updatePassword(@RequestParam @Pattern(regexp = "[a-fA-F0-9]{32}", message = "旧密码格式不正确") String oldPassword,
                                        @RequestParam @Pattern(regexp = "[a-fA-F0-9]{32}", message = "新密码格式不正确") String newPassword) {
        AuthUser authUser = UserContext.getCurrentUser();
        //校验当前用户是否存在
        User member = userClient.getById(authUser.getId());
        if (member == null) {
            throw new ServiceException(ResultCode.USER_NOT_EXIST);
        }
        this.walletService.updateUserWalletPassword(oldPassword, newPassword);
        return ResultUtil.data("修改成功");
    }


    @GetMapping(value = "/check")
    @ApiOperation(value = "检测会员是否设置过支付密码,会员中心设置或者修改密码时使用")
    public Boolean checkPassword() {
        return walletService.checkPassword();
    }


    @PreventDuplicateSubmissions
    @PostMapping(value = "/withdrawal")
    @ApiOperation(value = "会员中心余额提现")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "price", value = "提现金额", required = true, dataType = "double", paramType = "query")
    })
    public ResultMessage<Boolean> withdrawal(@Max(value = 9999, message = "充值金额单次最多允许提现9999元") @Min(value = 1, message = "充值金额单次最少提现金额为1元") Double price) {
        return ResultUtil.data(withdrawApplyService.applyWithdrawal(price));
    }

    @ApiOperation(value = "冲账接口-绿色积分")
    @GetMapping(value = "/strikeBalance")
    public ResultMessage<Object> strikeBalance (String userId) {
        walletService.strikeBalance(userId);
        return ResultUtil.success();
    }

    @ApiOperation(value = "冲账接口-余额")
    @GetMapping(value = "/strikeBalanceByRemainder")
    public ResultMessage<Object> strikeBalanceByRemainder (String userId) {
        walletService.strikeBalanceByRemainder(userId);
        return ResultUtil.success();
    }

    @ApiOperation(value = "分账余额对冲")
    @GetMapping(value = "/shareProfitStrike")
    public ResultMessage<Object> shareProfitStrike (String userId) {
        walletService.shareProfitStrike(userId);
        return ResultUtil.success();
    }

    @ApiOperation(value = "增加余额")
    @GetMapping(value = "/addBalance")
    public ResultMessage<Object> addBalance(String openId, String orderSn, Double money, String remark, String payType) {
        return walletService.addBalance(openId, orderSn, money, remark, payType);
    }
}
